class Xstore{

    constructor(){  
        
    }  

	/**
     * 存储localStorage
     * @param string name 缓存的键名，支持"wechat.user.name"格式来获取值，前提是缓存值是一个JSON字符串 
     * @param mixed content 缓存的内容
     * @param int time 缓存时间 单位：s; 若为null则表示永不过期，若为-1则表示过期但不删除原来内容
     */
     setStore(name, content, time=null) {
        let timestamp = time ? Date.parse(new Date())/1000 + parseInt(time):null
        if (!name) return;
        name = name.toString();
        let keys = name.split('.')
        let key = keys.shift()
        let str = window.localStorage.getItem(key)||{};//这里有一个坑爹的bug，JSON.parse(null)是不会报错的
        let value = {};

        try{
            value = JSON.parse(str)
        }catch(e){
            value = {
                data:str, 
                _endtime:0
            }
        }
        if(keys.length==0){
            value.data = content
        }else{
            let real_key = keys.join('.');
            value.data = this.set(value.data, real_key, content)
        }
        if(time != -1)value._endtime = timestamp;
        value = JSON.stringify(value);
        window.localStorage.setItem(key, value);
        return this.getStore(name);
    }

    /**
     * 实现类似 laravel Arr类中的数组操作，因为js中对象操作更方便，所以改为对象操作，另外，json序列化时数组非数字key会丢失
     * @example set({},'a.b.c','ddd') => {a:b:{c:'ddd'}}
     * @param {Object} array 被操作对象
     * @param {String} key key值
     * @param {Object} value 设置后返回值（因为js无法实现函数的传值引用，所以只能返回值再从函数外重新设置）
     */
    set(array,key,value){
        let arr = array; // 实现传值引用
        let keys = key.split('.');
        
        while (keys.length > 1) {
            key = keys.shift();
            
            // If the key doesn't exist at this depth, we will just create an empty array
            // to hold the next value, allowing us to create the arrays to hold final
            // values at the correct depth. Then we'll keep digging into the array.
            if (!arr.hasOwnProperty(key) || !(arr[key] instanceof Object)) {
                arr[key] = {};
            }
            arr = arr[key]; // php 请使用 $array = &$array[$key]
        }
        arr[keys.shift()] = value;

        return array;
    }
     /**
     * 实现类似 laravel Arr类中的数组操作，与set方法对应
     * @example sget({a:{b:{c:{d:123}}}},'a.b.c.d') => 123
     * @param {Object} $array 被操作对象
     * @param {String} $key key值
     * @param {Object} $default 设置后返回值（因为js无法实现函数的传值引用，所以只能返回值再从函数外重新设置）
     */
    get($array, $key, $default=null){
        if ($key===null) {
            return $array;
        }

        if ($array.hasOwnProperty($key)) {
            return $array[$key];
        }

        $key.split('.').forEach($segment => {
            if ($array.hasOwnProperty($segment)) {
                $array = $array[$segment];
            } else {
                return $default;
            }
        });

        return $array;
    }

    /**
     * 获取localStorage
     * @param string name 缓存的键名，支持"wechat.user.name"格式来获取值，前提是缓存值是一个JSON字符串 
     */
     getStore(name) {
        let timestamp = Date.parse(new Date())/1000
        if (!name) return;
        let key = name.split('.')[0]
        let str = window.localStorage.getItem(key)
        try{
            let val = JSON.parse(str)
            if( val._endtime && timestamp > val._endtime)return;
            if(!val.hasOwnProperty('data'))return;
            val = val.data
            name.split('.').forEach((segment, index) => {
                if(index > 0){
                    if(val.hasOwnProperty(segment)){
                        val = val[segment]
                    }
                }
            });
            return val;
        }catch(e){
            return false;
        }
    }
    /**
     * 删除localStorage, 若要设置过期请使用setStore(key, value, '-1')
     */
    removeStore(name) {
        if (!name) return;
        if(!this.getStore(name)) return true
        if(!this.setStore(name, null))return true
        return false
    }
}